import 'dart:async';
import 'dart:io';
import 'package:just_audio/just_audio.dart';
import 'package:flutter/foundation.dart';
import '../models/models.dart';
import 'database_service.dart';

/// 音频播放服务类
/// 负责音乐播放、暂停、切换、进度控制等核心功能
class AudioPlayerService extends ChangeNotifier {
  static final AudioPlayerService _instance = AudioPlayerService._internal();
  factory AudioPlayerService() => _instance;
  AudioPlayerService._internal();

  // 音频播放器实例
  final AudioPlayer _audioPlayer = AudioPlayer();
  final DatabaseService _databaseService = DatabaseService();

  // 播放状态
  bool _isPlaying = false;
  bool _isLoading = false;
  bool _isShuffleEnabled = false;
  bool _isRepeatEnabled = false;
  PlayMode _playMode = PlayMode.sequence;
  double _volume = 1.0;
  double _playbackSpeed = 1.0;

  // 当前播放信息
  Music? _currentMusic;
  List<Music> _playlist = [];
  int _currentIndex = 0;
  Duration _currentPosition = Duration.zero;
  Duration _totalDuration = Duration.zero;

  // 流订阅
  StreamSubscription<PlayerState>? _playerStateSubscription;
  StreamSubscription<Duration>? _positionSubscription;
  StreamSubscription<Duration?>? _durationSubscription;

  // 播放历史和统计
  DateTime? _playStartTime;
  Timer? _progressTimer;

  /// 初始化音频服务
  Future<void> init() async {
    await _setupAudioSession();
    _setupStreamSubscriptions();
  }

  /// 设置音频会话
  Future<void> _setupAudioSession() async {
    try {
      debugPrint('设置音频会话...');
      // 设置音频会话类别（iOS）
      if (Platform.isIOS) {
        // 不预先设置音频源，避免初始化问题
        debugPrint('iOS音频会话设置完成');
      }
      debugPrint('音频会话设置完成');
    } catch (e) {
      debugPrint('设置音频会话失败: $e');
    }
  }

  /// 设置流订阅
  void _setupStreamSubscriptions() {
    debugPrint('设置流订阅...');

    // 播放状态监听
    _playerStateSubscription = _audioPlayer.playerStateStream.listen((state) {
      debugPrint('播放状态变化: ${state.playing}, 处理状态: ${state.processingState}');
      _isPlaying = state.playing;
      _isLoading = state.processingState == ProcessingState.loading ||
          state.processingState == ProcessingState.buffering;

      // 播放完成处理
      if (state.processingState == ProcessingState.completed) {
        debugPrint('播放完成');
        _onPlaybackCompleted();
      }

      notifyListeners();
    }, onError: (error) {
      debugPrint('播放状态流错误: $error');
    });

    // 播放位置监听
    _positionSubscription = _audioPlayer.positionStream.listen((position) {
      _currentPosition = position;
      notifyListeners();
    }, onError: (error) {
      debugPrint('位置流错误: $error');
    });

    // 总时长监听
    _durationSubscription = _audioPlayer.durationStream.listen((duration) {
      if (duration != null) {
        debugPrint('时长更新: ${duration.inSeconds}s');
        _totalDuration = duration;
        notifyListeners();
      }
    }, onError: (error) {
      debugPrint('时长流错误: $error');
    });

    debugPrint('流订阅设置完成');
  }

  /// 播放音乐
  Future<void> playMusic(Music music,
      {List<Music>? playlist, int? index}) async {
    try {
      debugPrint('开始播放音乐: ${music.title}');
      _isLoading = true;
      notifyListeners();

      // 更新播放列表
      if (playlist != null) {
        _playlist = playlist;
        _currentIndex = index ?? 0;
      } else {
        _playlist = [music];
        _currentIndex = 0;
      }

      _currentMusic = music;
      _playStartTime = DateTime.now();

      // 设置音频源 - 支持本地文件和在线URL
      Uri audioUri;
      if (music.filePath.startsWith('http://') ||
          music.filePath.startsWith('https://')) {
        // 在线音频URL
        audioUri = Uri.parse(music.filePath);
        debugPrint('在线音频URL: $audioUri');
      } else {
        // 本地文件路径
        audioUri = Uri.file(music.filePath);
        debugPrint('本地文件路径: $audioUri');
      }

      debugPrint('设置音频源...');
      try {
        if (music.filePath.startsWith('http://') ||
            music.filePath.startsWith('https://')) {
          // 在线音频URL
          await _audioPlayer.setUrl(music.filePath);
        } else {
          // 本地文件路径
          await _audioPlayer.setFilePath(music.filePath);
        }
        debugPrint('音频源设置完成');
      } catch (e) {
        debugPrint('设置音频源失败，尝试使用Uri方式: $e');
        await _audioPlayer.setAudioSource(
          AudioSource.uri(audioUri),
        );
        debugPrint('音频源设置完成(Uri方式)');
      }

      // 开始播放
      debugPrint('开始播放...');
      await _audioPlayer.play();
      debugPrint('播放命令发送完成');

      // 更新播放次数
      await _updatePlayCount(music);

      // 开始进度计时
      _startProgressTimer();

      _isLoading = false;
      notifyListeners();
    } catch (e) {
      debugPrint('播放音乐失败: $e');
      _isLoading = false;
      _isPlaying = false;
      notifyListeners();
    }
  }

  /// 暂停播放
  Future<void> pause() async {
    await _audioPlayer.pause();
    _isPlaying = false;
    _stopProgressTimer();
    notifyListeners();
  }

  /// 恢复播放
  Future<void> resume() async {
    await _audioPlayer.play();
    _isPlaying = true;
    _startProgressTimer();
    notifyListeners();
  }

  /// 停止播放
  Future<void> stop() async {
    await _audioPlayer.stop();
    _stopProgressTimer();
    _savePlayHistory();
    _currentMusic = null;
    _currentPosition = Duration.zero;
    notifyListeners();
  }

  /// 设置播放列表
  Future<void> setPlaylist(List<Music> playlist, {int initialIndex = 0}) async {
    try {
      _playlist = playlist;
      _currentIndex = initialIndex;

      if (playlist.isNotEmpty && initialIndex < playlist.length) {
        _currentMusic = playlist[initialIndex];

        // 设置音频源 - 支持本地文件和在线URL
        Uri audioUri;
        if (_currentMusic!.filePath.startsWith('http://') ||
            _currentMusic!.filePath.startsWith('https://')) {
          // 在线音频URL
          audioUri = Uri.parse(_currentMusic!.filePath);
        } else {
          // 本地文件路径
          audioUri = Uri.file(_currentMusic!.filePath);
        }

        await _audioPlayer.setAudioSource(AudioSource.uri(audioUri));
      }

      notifyListeners();
    } catch (e) {
      debugPrint('设置播放列表失败: $e');
    }
  }

  /// 开始播放
  Future<void> play() async {
    try {
      await _audioPlayer.play();
    } catch (e) {
      debugPrint('播放失败: $e');
    }
  }

  /// 播放下一首
  Future<void> playNext() async {
    if (_playlist.isEmpty) return;

    int nextIndex;
    if (_isShuffleEnabled) {
      // 随机播放
      nextIndex = _getRandomIndex();
    } else {
      // 顺序播放
      nextIndex = (_currentIndex + 1) % _playlist.length;
    }

    if (nextIndex < _playlist.length) {
      _currentIndex = nextIndex;
      await playMusic(_playlist[nextIndex],
          playlist: _playlist, index: nextIndex);
    }
  }

  /// 播放上一首
  Future<void> playPrevious() async {
    if (_playlist.isEmpty) return;

    int previousIndex;
    if (_isShuffleEnabled) {
      // 随机播放
      previousIndex = _getRandomIndex();
    } else {
      // 顺序播放
      previousIndex = (_currentIndex - 1 + _playlist.length) % _playlist.length;
    }

    if (previousIndex >= 0) {
      _currentIndex = previousIndex;
      await playMusic(_playlist[previousIndex],
          playlist: _playlist, index: previousIndex);
    }
  }

  /// 跳转到指定位置
  Future<void> seekTo(Duration position) async {
    await _audioPlayer.seek(position);
  }

  /// 设置音量
  Future<void> setVolume(double volume) async {
    _volume = volume.clamp(0.0, 1.0);
    await _audioPlayer.setVolume(_volume);
    notifyListeners();
  }

  /// 设置播放速度
  Future<void> setPlaybackSpeed(double speed) async {
    _playbackSpeed = speed.clamp(0.5, 2.0);
    await _audioPlayer.setSpeed(_playbackSpeed);
    notifyListeners();
  }

  /// 切换随机播放
  void toggleShuffle() {
    _isShuffleEnabled = !_isShuffleEnabled;
    notifyListeners();
  }

  /// 切换重复播放
  void toggleRepeat() {
    _isRepeatEnabled = !_isRepeatEnabled;
    notifyListeners();
  }

  /// 设置播放模式
  void setPlayMode(PlayMode mode) {
    _playMode = mode;
    _isShuffleEnabled = mode == PlayMode.shuffle;
    _isRepeatEnabled = mode == PlayMode.repeatAll || mode == PlayMode.repeatOne;
    notifyListeners();
  }

  /// 播放完成处理
  void _onPlaybackCompleted() {
    _savePlayHistory();

    switch (_playMode) {
      case PlayMode.repeatOne:
        // 单曲循环
        if (_currentMusic != null) {
          playMusic(_currentMusic!, playlist: _playlist, index: _currentIndex);
        }
        break;
      case PlayMode.repeatAll:
      case PlayMode.sequence:
      case PlayMode.shuffle:
        // 播放下一首
        playNext();
        break;
    }
  }

  /// 获取随机索引
  int _getRandomIndex() {
    if (_playlist.length <= 1) return 0;
    int randomIndex;
    do {
      randomIndex = (DateTime.now().millisecondsSinceEpoch % _playlist.length);
    } while (randomIndex == _currentIndex && _playlist.length > 1);
    return randomIndex;
  }

  /// 开始进度计时
  void _startProgressTimer() {
    _progressTimer?.cancel();
    _progressTimer = Timer.periodic(const Duration(seconds: 1), (timer) {
      // 每秒更新一次进度，用于统计播放时长
    });
  }

  /// 停止进度计时
  void _stopProgressTimer() {
    _progressTimer?.cancel();
    _progressTimer = null;
  }

  /// 更新播放次数
  Future<void> _updatePlayCount(Music music) async {
    try {
      final updatedMusic = music.copyWith(
        playCount: music.playCount + 1,
        updatedAt: DateTime.now(),
      );
      await _databaseService.updateMusic(updatedMusic);
    } catch (e) {
      debugPrint('更新播放次数失败: $e');
    }
  }

  /// 保存播放历史
  Future<void> _savePlayHistory() async {
    if (_currentMusic == null || _playStartTime == null) return;

    try {
      final playDuration = DateTime.now().difference(_playStartTime!);
      final progress = _totalDuration.inMilliseconds > 0
          ? _currentPosition.inMilliseconds / _totalDuration.inMilliseconds
          : 0.0;

      final history = PlayHistory(
        id: 'history_${DateTime.now().millisecondsSinceEpoch}',
        musicId: _currentMusic!.id,
        playedAt: _playStartTime!,
        playDuration: playDuration.inMilliseconds,
        completed: progress >= 0.8, // 播放80%以上算完成
        progress: progress,
        source: 'player',
      );

      await _databaseService.insertPlayHistory(history);

      // 更新播放统计
      await _updatePlayStatistics(playDuration.inMilliseconds);
    } catch (e) {
      debugPrint('保存播放历史失败: $e');
    }
  }

  /// 更新播放统计
  Future<void> _updatePlayStatistics(int playDuration) async {
    if (_currentMusic == null) return;

    try {
      // 检查是否是今天
      final now = DateTime.now();
      final today = DateTime(now.year, now.month, now.day);
      final playTime = DateTime(_playStartTime?.year ?? now.year,
          _playStartTime?.month ?? now.month, _playStartTime?.day ?? now.day);
      final isToday = today.isAtSameMomentAs(playTime);

      await _databaseService.incrementPlayStatistics(
        playTime: playDuration,
        musicId: _currentMusic!.id,
        isToday: isToday,
      );
    } catch (e) {
      debugPrint('更新播放统计失败: $e');
    }
  }

  /// 获取播放进度百分比
  double get progressPercentage {
    if (_totalDuration.inMilliseconds == 0) return 0.0;
    return _currentPosition.inMilliseconds / _totalDuration.inMilliseconds;
  }

  /// 格式化时间显示
  String formatDuration(Duration duration) {
    String twoDigits(int n) => n.toString().padLeft(2, '0');
    final hours = duration.inHours;
    final minutes = duration.inMinutes.remainder(60);
    final seconds = duration.inSeconds.remainder(60);

    if (hours > 0) {
      return '${twoDigits(hours)}:${twoDigits(minutes)}:${twoDigits(seconds)}';
    } else {
      return '${twoDigits(minutes)}:${twoDigits(seconds)}';
    }
  }

  /// 获取当前播放位置文本
  String get currentPositionText => formatDuration(_currentPosition);

  /// 获取总时长文本
  String get totalDurationText => formatDuration(_totalDuration);

  /// 检查是否有下一首
  bool get hasNext {
    if (_playlist.isEmpty) return false;
    if (_isShuffleEnabled || _isRepeatEnabled) return true;
    return _currentIndex < _playlist.length - 1;
  }

  /// 检查是否有上一首
  bool get hasPrevious {
    if (_playlist.isEmpty) return false;
    if (_isShuffleEnabled || _isRepeatEnabled) return true;
    return _currentIndex > 0;
  }

  // Getters
  bool get isPlaying => _isPlaying;
  bool get isLoading => _isLoading;
  bool get isShuffleEnabled => _isShuffleEnabled;
  bool get isRepeatEnabled => _isRepeatEnabled;
  PlayMode get playMode => _playMode;
  double get volume => _volume;
  double get playbackSpeed => _playbackSpeed;
  Music? get currentMusic => _currentMusic;
  List<Music> get playlist => List.unmodifiable(_playlist);
  int get currentIndex => _currentIndex;
  Duration get currentPosition => _currentPosition;
  Duration get totalDuration => _totalDuration;

  /// 添加音乐到播放队列
  void addToQueue(Music music) {
    _playlist.add(music);
    notifyListeners();
  }

  /// 添加多首音乐到播放队列
  void addAllToQueue(List<Music> musicList) {
    _playlist.addAll(musicList);
    notifyListeners();
  }

  /// 从队列中移除音乐
  void removeFromQueue(int index) {
    if (index >= 0 && index < _playlist.length) {
      _playlist.removeAt(index);
      if (_currentIndex > index) {
        _currentIndex--;
      } else if (_currentIndex == index) {
        // 如果移除的是当前播放的音乐，停止播放
        stop();
      }
      notifyListeners();
    }
  }

  /// 清空播放队列
  void clearQueue() {
    stop();
    _playlist.clear();
    _currentIndex = 0;
    _currentMusic = null;
    notifyListeners();
  }

  /// 释放资源
  @override
  void dispose() {
    _playerStateSubscription?.cancel();
    _positionSubscription?.cancel();
    _durationSubscription?.cancel();
    _progressTimer?.cancel();
    _audioPlayer.dispose();
    super.dispose();
  }
}

/// PlayMode扩展方法
extension PlayModeExtension on PlayMode {
  /// 获取显示名称
  String get displayName {
    switch (this) {
      case PlayMode.sequence:
        return '顺序播放';
      case PlayMode.shuffle:
        return '随机播放';
      case PlayMode.repeatAll:
        return '列表循环';
      case PlayMode.repeatOne:
        return '单曲循环';
    }
  }

  /// 获取图标名称
  String get iconName {
    switch (this) {
      case PlayMode.sequence:
        return 'list_music';
      case PlayMode.shuffle:
        return 'shuffle';
      case PlayMode.repeatAll:
        return 'repeat';
      case PlayMode.repeatOne:
        return 'repeat_one';
    }
  }

  /// 获取下一个播放模式
  PlayMode get next {
    switch (this) {
      case PlayMode.sequence:
        return PlayMode.shuffle;
      case PlayMode.shuffle:
        return PlayMode.repeatAll;
      case PlayMode.repeatAll:
        return PlayMode.repeatOne;
      case PlayMode.repeatOne:
        return PlayMode.sequence;
    }
  }
}
